﻿#ifndef BLINN_SHADING
#define BLINN_SHADING

#include "includes\\CommonResources.fx"


float GetDistanceMod(float3 objectPos, float3 lightPos)
{
	float baseMod = length(lightPos) * 1.1f;
	float lightDistance = distance(lightPos, objectPos);
	return (baseMod * baseMod) / (lightDistance * lightDistance);
}


void BlinnShading(float3 objectPos,
		    float3 normal,
		    float3 lightPos,
		    float3 cameraPos,
			float specularPower,
		    out float diffuseIntensity,
		    out float specularIntensity)
{
	float3 lightVec = normalize(lightPos - objectPos);
	float3 cameraVec = normalize(cameraPos - objectPos);
	float3 halfVec = normalize(cameraVec + lightVec);
	
	float distanceMod = GetDistanceMod(objectPos, lightPos);
	float dotLN = saturate(dot(lightVec, normal));
	float dotHN = saturate(dot(halfVec, normal));

	diffuseIntensity = dotLN * distanceMod;
	specularIntensity = pow(dotHN, specularPower) * distanceMod;
}


float3 GetDiffuseGlobalLightValue(float diffuseIntensity)
{
	float intensity = diffuseIntensity * cGlobalLightDiffuseFactor + cGlobalLightAmbientFactor;
	return cGlobalLightColor * intensity;
}


float3 GetSpecularGlobalLightValue(float specularIntensity)
{
	return specularIntensity * cGlobalLightColor;
}


float3 GetBlinnShadedColor(float3 objectColor, 
			float3 objectPos,
		    float3 normal,
		    float3 lightPos,
			float specularPower,
			float diffuseMod = 1.0f,
			float specularMod = 1.0f)
{
	float diffuseIntensity, specularIntensity;
	BlinnShading(objectPos, normal, lightPos, xCameraPosition, specularPower, diffuseIntensity, specularIntensity);
	return objectColor.rgb  * GetDiffuseGlobalLightValue(diffuseIntensity).rgb * diffuseMod
		+ GetSpecularGlobalLightValue(specularIntensity) * specularMod;
}

#endif
